    using System;
using System.Collections.Generic;
using System.Linq;
using System.Web;
using System.Web.Mvc;
using LetLord.Models;
using WebMatrix.WebData;
using System.IO;

using LetLord.ViewModels;

namespace LetLord.Controllers
{
    public class TenantsController : Controller
    {
        private LetLordContext db;
        private readonly ITenantRepository tenantRepository;
        private readonly ITenantGroupMemberRepository tenantGMRepository;
        private readonly IReferencePhotoRepository refPhotoRepository;

        // If you are using Dependency Injection, you can delete the following constructor
        public TenantsController()
            : this(new TenantRepository(), new TenantGroupMemberRepository(), new ReferencePhotoRepository())
        {
        }

        public TenantsController(ITenantRepository tenantRepository, ITenantGroupMemberRepository tenantGMRepository, IReferencePhotoRepository refPhotoRepository)
        {
            this.db = new LetLordContext();
            this.tenantRepository = tenantRepository;
            this.tenantGMRepository = tenantGMRepository;
            this.refPhotoRepository = refPhotoRepository;
        }

        //
        // GET: /Tenants/Profile

        public ActionResult MyProfile()
        {
            var currentTenant = tenantRepository.GetLoggedInTenant();

            return View(currentTenant);
        }

        //
        // GET: /Tenants/EditTenantDetails

        [HttpGet]
        public ActionResult EditTenantDetails()
        {
            return PartialView("_EditTenantDetailsPartial", tenantRepository.GetLoggedInTenant());
        }

        //
        // POST: /Tenants/EditTenantDetails

        [HttpPost]
        public ActionResult EditTenantDetails(Tenant tenant)
        {
            if (ModelState.IsValid)
            {
                tenantRepository.InsertOrUpdate(tenant);
                tenantRepository.Save();
                return PartialView("_TenantDetailsPartial", tenant);
            }
            else
            {
                return View("Error");
            }
        }

        //
        // GET: /Tenants/EditTenantPropertyAttributes

        [HttpGet]
        public ActionResult EditTenantPropertyAttributes()
        {
            return PartialView("_EditTenantPropertyAttributesPartial", tenantRepository.GetLoggedInTenant());
        }

        //
        // POST: /Tenants/EditTenantPropertyAttributes

        [HttpPost]
        public ActionResult EditTenantPropertyAttributes(Tenant tenant)
        {
            if (ModelState.IsValid)
            {
                var currentTenant = tenantRepository.GetLoggedInTenant();

                currentTenant.DesiredPropertyLocation = tenant.DesiredPropertyLocation;
                currentTenant.MinBudget = tenant.MinBudget;
                currentTenant.MaxBudget = tenant.MaxBudget;
                currentTenant.DesiredNumberOfBedrooms = tenant.DesiredNumberOfBedrooms;
                currentTenant.IsProfessional = tenant.IsProfessional;
                currentTenant.IsStudent = tenant.IsStudent;
                currentTenant.HasChildren = tenant.HasChildren;
                currentTenant.HasRentAllowance = tenant.HasRentAllowance;
                currentTenant.IsInGroup = tenant.IsInGroup;
                currentTenant.HasPets = tenant.HasPets;

                tenantRepository.InsertOrUpdate(currentTenant);
                tenantRepository.Save();
                return PartialView("_TenantPropertyAttributesPartial", currentTenant);
            }
            else
            {
                return View("Error");
            }
        }

        // GET: /Tenants/TenantUploadReference

        [HttpGet]
        public ActionResult TenantUploadReference()
        {
            try
            {
                return PartialView("_TenantUploadReferencePartial", tenantRepository.GetLoggedInTenant());
            }
            catch (Exception e)
            {
                ModelState.AddModelError("", e);
                return View("Error");
            }
        }

        // GET: /Tenants/TenantUploadReference

        [HttpPost]
        public ActionResult TenantUploadReference(HttpPostedFileBase fileData, Tenant tenant)
        {
            try
            {
                if (fileData != null)
                {
                    var supportedTypes = new[] { "jpg", "jpeg", "png", "JPG", "JPEG", "PNG" };
                    var fileExt = System.IO.Path.GetExtension(fileData.FileName).Substring(1);

                    if (!supportedTypes.Contains(fileExt))
                    {
                        ModelState.AddModelError("photo", "Invalid type. Only the following types (jpg, jpeg, png) are supported.");
                        return View("Error");
                    }

                    using (var db = new LetLordContext())
                    {
                        var reference = db.Image.Create<ReferencePhoto>();

                        // Convert HttpPostedFileBase to byte array
                        MemoryStream target = new MemoryStream();
                        fileData.InputStream.CopyTo(target);
                        byte[] photo = target.ToArray();

                        reference.UserId = tenantRepository.GetLoggedInTenant().UserId;
                        reference.File = photo;
                        reference.Format = fileExt;
                        reference.DateUploaded = DateTime.Now.Date;
                        reference.Description = "";
                        reference.Name = "";

                        db.Image.Add(reference);
                        db.SaveChanges();

                        return PartialView("_TenantReferencePhotosPartial", tenant);
                    }
                }
                else
                {
                    return View("Error");
                }
            }
            catch (Exception e)
            {
                ModelState.AddModelError("", e);
                return View("Error");
            }
        }

        [HttpGet]
        public ActionResult GetReference(int id)
        {
            byte[] reference = tenantRepository.GetReference(id);
            var format = db.Image.SingleOrDefault(x => x.ImageId == id).Format;
            if (reference == null)
            {
                return HttpNotFound();
            }
            return File(reference, format);
        }

        // GET: /Tenants/DeleteReference
        [HttpGet]
        public ActionResult DeleteReference(int id)
        {
            return View(refPhotoRepository.Find(id));
        }

        // POST: /Tenants/DeleteReference
        [HttpPost, ActionName("DeleteReference")]
        public ActionResult DeleteReferenceConfirmed(int id)
        {
            try
            {
                refPhotoRepository.Delete(id);
                refPhotoRepository.Save();
                return PartialView("_TenantReferencePhotosPartial", tenantRepository.GetLoggedInTenant());
            }
            catch (Exception e)
            {
                e.InnerException.ToString();
            }
            return View("Error");
        }


        // GET: /Tenants/TenantViewings
        [HttpGet]
        public ActionResult TenantViewings()
        {
            var currentTenant = tenantRepository.GetLoggedInTenant();
            return PartialView("_TenantViewingsPartial", currentTenant);
        }

        // GET: /Tenants/TenantSavedProperties
        [HttpGet]
        public ActionResult TenantSavedProperties()
        {
            var currentTenant = tenantRepository.GetLoggedInTenant();
            return PartialView("_TenantSavedPropertiesPartial", currentTenant);
        }

        // GET: /Tenants/TenantGroupMembers
        [HttpGet]
        public ActionResult TenantGroupMembers()
        {
            try
            {
                return PartialView("_CreateTenantGroupMemberPartial");
            }
            catch (Exception e)
            {
                ModelState.AddModelError("", e);
            }
            return View("_InsertUpdateTenantGroupMembersPartial");
        }

        [HttpPost]
        public ActionResult CreateTenantGroupMember(CreateTenantGroupMemberViewMemberModel viewModel)
        {
            if (ModelState.IsValid)
            {
                try
                {
                    var newTGM = new TenantGroupMember();
                    newTGM.TenantGroupMemberName = viewModel.TenantGroupMemberName;
                    newTGM.TenantGroupMemberAge = viewModel.TenantGroupMemberAge;
                    newTGM.UserId = tenantRepository.GetLoggedInTenant().UserId;
                    tenantGMRepository.InsertOrUpdate(newTGM);
                    return PartialView("_InsertUpdateTenantGroupMembersPartial");
                }
                catch (Exception e)
                {
                    ModelState.AddModelError("Validation error", e.Message + "\n" + e.InnerException);
                }
            }
            return View("Error");
        }

        // GET: /Tenants/EditMember
        [HttpGet]
        public ActionResult EditMember(int id)
        {
            try
            {
                var viewModel = new EditTenantGroupMemberViewModel();
                viewModel.Id = id;
                return PartialView("_EditMemberPartial", viewModel);
            }
            catch (Exception e)
            {
                e.InnerException.ToString();
            }
            return View("Error");
        }

        // POST: /Tenants/
        [HttpPost]
        public ActionResult EditMember(EditTenantGroupMemberViewModel viewModel)
        {
            if (ModelState.IsValid)
            {
                try
                {
                    var toUpdate = tenantGMRepository.Find(viewModel.Id);
                    toUpdate.TenantGroupMemberName = viewModel.Name;
                    toUpdate.TenantGroupMemberAge = viewModel.Age;
                    tenantGMRepository.InsertOrUpdate(toUpdate);
                    tenantGMRepository.Save();
                    return Json(new { error = false, message = "Member edited" });
                }
                catch (Exception e)
                {
                    e.InnerException.ToString();
                }
            }
            else
            {
                ModelState.AddModelError("", "");
            }
            return View("Error");
        }

        [HttpPost]
        public ActionResult DeleteMember(int id)
        {
            try
            {
                tenantGMRepository.Delete(id);
                tenantGMRepository.Save();
                return PartialView("_TenantGroupMembersPartial", tenantRepository.GetLoggedInTenant());
            }
            catch(Exception e)
            {
                e.InnerException.ToString();
            }
            return View("Error");
        }

        [HttpGet]
        public ActionResult ViewProfile(int id)
        {
            try
            {
                return PartialView("_ViewProfilePartial", tenantRepository.Find(id));
            }
            catch (Exception e)
            {
                e.InnerException.ToString();
            }
            return View("Error");
        }

        protected override void Dispose(bool disposing)
        {
            if (disposing)
            {
                tenantRepository.Dispose();
                tenantGMRepository.Dispose();
                db.Dispose();
            }
            base.Dispose(disposing);
        }
    }
}

